package kwic.architecture;

import java.io.*;
import java.util.*;

/**
 * 面向对象体系结构实现KWIC。
 */
public class ObjectOriented {
    public static void main(String[] args) {
        Input input = new Input("src/main/resources/input.txt");
        input.readInput();

        Shift shift = new Shift(input.getLines());
        shift.generateShifts();

        Alphabetizer alphabetizer = new Alphabetizer(shift.getShifts());
        alphabetizer.sortShifts();

        Output output = new Output(alphabetizer.getSortedShifts(), "src/main/resources/output3.txt");
        output.writeOutput();
    }
}

class Input {
    private String fileName;
    private ArrayList<String> lines = new ArrayList<>();

    public Input(String fileName) {
        this.fileName = fileName;
    }

    public ArrayList<String> getLines() {
        return lines;
    }

    public void readInput() {
        try (BufferedReader inputFile = new BufferedReader(new FileReader(fileName))) {
            String line;
            while ((line = inputFile.readLine()) != null) {
                lines.add(line);
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

class Shift {
    private ArrayList<String> lines;
    private ArrayList<String> shifts = new ArrayList<>();

    public Shift(ArrayList<String> lines) {
        this.lines = lines;
    }

    public ArrayList<String> getShifts() {
        return shifts;
    }

    public void generateShifts() {
        for (String line : lines) {
            StringTokenizer token = new StringTokenizer(line);
            ArrayList<String> tokens = new ArrayList<>();
            while (token.hasMoreTokens()) {
                tokens.add(token.nextToken());
            }
            for (int i = 0; i < tokens.size(); i++) {
                String shiftedLine = String.join(" ", tokens);
                shifts.add(shiftedLine);
                Collections.rotate(tokens, -1);
            }
        }
    }
}

class Alphabetizer {
    private ArrayList<String> shifts;

    public Alphabetizer(ArrayList<String> shifts) {
        this.shifts = shifts;
    }

    public ArrayList<String> getSortedShifts() {
        return shifts;
    }

    public void sortShifts() {
        shifts.sort(String::compareToIgnoreCase);
    }
}

class Output {
    private ArrayList<String> sortedShifts;
    private String fileName;

    public Output(ArrayList<String> sortedShifts, String fileName) {
        this.sortedShifts = sortedShifts;
        this.fileName = fileName;
    }

    public void writeOutput() {
        try (BufferedWriter outputFile = new BufferedWriter(new FileWriter(fileName))) {
            for (String line : sortedShifts) {
                outputFile.write(line + "\n");
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}
